package com.netease.nie.service;

import java.beans.IntrospectionException;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Pattern;

import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.netease.nie.base.cache.CacheParam;
import com.netease.nie.base.cache.DataOperation;
import com.netease.nie.base.cache.redis.RedisManager;
import com.netease.nie.base.exceptions.BusinessException;
import com.netease.nie.base.protocol.SystemResponseCode;
import com.netease.nie.base.utils.ConvertUtils;
import com.netease.nie.base.utils.CopyUtils;
import com.netease.nie.constants.BusinessConstants;
import com.netease.nie.constants.CachePrefixConstants;
import com.netease.nie.dao.UserDao;
import com.netease.nie.dto.UserInfoDto;
import com.netease.nie.model.User;

@Service
public class UserInfoServiceImpl implements UserInfoService {

	@Autowired
	private UserDao userDao;
	
	private static final String USER_INFO_PREFIX = CachePrefixConstants.UserPrefix.USER_INFO_PREFIX;
	//正则表达式：验证手机号
    public static final String REGEX_MOBILE = "^1\\d{10}$";
	
	public UserInfoDto edit(long userId) {
		User user = queryUserByUserId(userId);
		UserInfoDto userInfoDto = new UserInfoDto();
		CopyUtils.copy(userInfoDto, user);
		
		int birthday = user.getBirthday();
		String birthdayStr = String.valueOf(birthday);
		userInfoDto.setBirthday(birthdayStr);
		
		return userInfoDto;
	}
	
	public User queryUserByUserId(Long userId) {
		RedisManager redisManager = buildRedisManager(userId);
		User user = redisManager.passiveOperateCache(User.class);
		return user;
	}


	public int save(UserInfoDto userInfoDto) {
		validDto(userInfoDto);
		
		User user = new User();
		CopyUtils.copy(user, userInfoDto);
		
		String birthdayStr = userInfoDto.getBirthday();
		if (StringUtils.isNotBlank(birthdayStr)) {
			int birthday = Integer.valueOf(birthdayStr);
			user.setBirthday(birthday);
		}
		
		int result = userDao.saveUserInfo(user);
		
		/**
		 * 更新缓存
		 */
		if (result > 0) {
			Long userId = user.getUserId();
			RedisManager redisManager = buildRedisManager(userId);
			redisManager.activeOperateCache();	//激活被动刷新
		}
		
		return result;
	}

	private void validDto(UserInfoDto userInfoDto) {
		if (userInfoDto == null)
			throw new BusinessException(SystemResponseCode.PARAM_VALUE_ILLEGAL.getCode(),
					"用户不存在");
		
		if(!Pattern.matches(REGEX_MOBILE, userInfoDto.getMobile()))
			throw new BusinessException(SystemResponseCode.PARAM_VALUE_ILLEGAL.getCode(),
					"请输入有效的手机号！");
	}
	
	private RedisManager buildRedisManager(final Long userId) {
		DataOperation dataOperation = new DataOperation() {	//如果缓存没有，则需要去数据库取数据
			public Object operate() {
				User user = userDao.queryUserInfoByUserId(userId);
				if (user == null)
					throw new BusinessException(BusinessConstants.USER_NOT_EXISTS.getCode(),
							"用户不存在");
				return user;
			}
		};
		String userInfoKey = USER_INFO_PREFIX + userId;
		List<String> keyList = new ArrayList<>();
		keyList.add(userInfoKey);
		CacheParam cacheParam = new CacheParam();
		cacheParam.setKeyList(keyList);
		cacheParam.setPrefix(USER_INFO_PREFIX);
		try {
			String[] fields = ConvertUtils
					.getJavaBeanProperties(User.class);
			cacheParam.setHashFields(fields);
		} catch (InstantiationException | IllegalAccessException | IntrospectionException e) {
			
		}

		return new RedisManager(cacheParam, dataOperation);
	}
}
